import requests
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
import json
import os
from typing import Optional, Dict, Any
import openai
from pathlib import Path


def get_msn_content(url: str = "https://www.msn.cn/zh-cn/money/watchlist?tab=Related&id=a3oxnm") -> str:
    """
    从MSN网站获取指定XPath元素的内容
    
    Args:
        url: 目标网页URL
        
    Returns:
        获取到的内容字符串
    """
    try:
        # 配置Chrome选项
        chrome_options = Options()
        chrome_options.add_argument("--headless")  # 无头模式
        chrome_options.add_argument("--no-sandbox")
        chrome_options.add_argument("--disable-dev-shm-usage")
        chrome_options.add_argument("--disable-gpu")
        chrome_options.add_argument("--window-size=1920,1080")
        
        # 创建WebDriver
        driver = webdriver.Chrome(options=chrome_options)
        
        # 访问网页
        driver.get(url)
        
        # 等待页面加载
        wait = WebDriverWait(driver, 10)
        
        # 定位目标元素
        xpath = '//*[@id="fdc_header"]/div/div[1]/div[1]/div[3]/div/div/div/div/div[1]'
        element = wait.until(EC.presence_of_element_located((By.XPATH, xpath)))
        
        # 获取内容
        content = element.text
        
        # 打印内容
        print("获取到的内容:")
        print(content)
        
        return content
        
    except Exception as e:
        print(f"获取内容时出错: {e}")
        return ""
    finally:
        if 'driver' in locals():
            driver.quit()


class OpenAIClient:
    """OpenAI API客户端类"""
    
    def __init__(self, config_file: str = "config.json"):
        """
        初始化OpenAI客户端
        
        Args:
            config_file: 配置文件路径
        """
        self.config_file = config_file
        self.api_key = None
        self.base_url = None
        self.client = None
        self.load_config()
        
    def load_config(self):
        """加载配置文件"""
        try:
            if os.path.exists(self.config_file):
                with open(self.config_file, 'r', encoding='utf-8') as f:
                    config = json.load(f)
                    self.api_key = config.get('openai_api_key')
                    self.base_url = config.get('openai_base_url', 'https://api.openai.com/v1')
                    
                if self.api_key and self.api_key != "your_openai_api_key_here":
                    self.client = openai.OpenAI(
                        api_key=self.api_key,
                        base_url=self.base_url
                    )
                else:
                    print("警告: 配置文件中未找到有效的openai_api_key")
            else:
                print(f"配置文件 {self.config_file} 不存在")
                print("请参考 config.example.json 创建配置文件")
        except Exception as e:
            print(f"加载配置文件时出错: {e}")
    
    def chat_completion(self, 
                       messages: list, 
                       model: str = "gpt-3.5-turbo",
                       temperature: float = 0.7,
                       max_tokens: Optional[int] = None) -> Dict[str, Any]:
        """
        发送聊天完成请求
        
        Args:
            messages: 消息列表
            model: 模型名称
            temperature: 温度参数
            max_tokens: 最大token数
            
        Returns:
            API响应结果
        """
        if not self.client:
            return {"error": "OpenAI客户端未初始化，请检查配置文件"}
        
        try:
            params = {
                "model": model,
                "messages": messages,
                "temperature": temperature
            }
            
            if max_tokens:
                params["max_tokens"] = max_tokens
            
            response = self.client.chat.completions.create(**params)
            return {
                "content": response.choices[0].message.content,
                "usage": response.usage.dict() if response.usage else None,
                "model": response.model
            }
        except Exception as e:
            return {"error": f"API请求失败: {e}"}
    
    def text_completion(self,
                       prompt: str,
                       model: str = "text-davinci-003",
                       temperature: float = 0.7,
                       max_tokens: Optional[int] = None) -> Dict[str, Any]:
        """
        发送文本完成请求
        
        Args:
            prompt: 提示文本
            model: 模型名称
            temperature: 温度参数
            max_tokens: 最大token数
            
        Returns:
            API响应结果
        """
        if not self.client:
            return {"error": "OpenAI客户端未初始化，请检查配置文件"}
        
        try:
            params = {
                "model": model,
                "prompt": prompt,
                "temperature": temperature
            }
            
            if max_tokens:
                params["max_tokens"] = max_tokens
            
            response = self.client.completions.create(**params)
            return {
                "content": response.choices[0].text.strip(),
                "usage": response.usage.dict() if response.usage else None,
                "model": response.model
            }
        except Exception as e:
            return {"error": f"API请求失败: {e}"}
    
    def embeddings(self, text: str, model: str = "text-embedding-ada-002") -> Dict[str, Any]:
        """
        获取文本嵌入向量
        
        Args:
            text: 输入文本
            model: 嵌入模型名称
            
        Returns:
            API响应结果
        """
        if not self.client:
            return {"error": "OpenAI客户端未初始化，请检查配置文件"}
        
        try:
            response = self.client.embeddings.create(
                model=model,
                input=text
            )
            return {
                "embedding": response.data[0].embedding,
                "usage": response.usage.dict() if response.usage else None,
                "model": response.model
            }
        except Exception as e:
            return {"error": f"API请求失败: {e}"}
    
    def get_gold_investment_analysis(self, 
                                   model: str = "moonshot-v1-8k",
                                   temperature: float = 0.7) -> Dict[str, Any]:
        """
        获取黄金投资收益分析语句
        
        Args:
            model: 使用的模型名称
            temperature: 温度参数
            
        Returns:
            包含分析结果的字典
        """
        if not self.client:
            return {"error": "OpenAI客户端未初始化，请检查配置文件"}
        
        try:
            # 首先获取实时金价
            from gold_price_fetcher import get_cngold_realtime_price
            
            try:
                gold_price, time_str, source = get_cngold_realtime_price()
                if gold_price <= 0:
                    # 如果获取失败，使用备选方案
                    gold_price, time_str = get_real_time_gold_price()
                    source = "备选数据源"
            except:
                # 如果都失败，使用模拟数据
                from datetime import datetime
                import random
                gold_price = round(550 + random.uniform(-20, 20), 2)
                time_str = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
                source = "模拟数据"
            
            # 构建专业的黄金投资分析prompt
            prompt = f"""
你是一位专业的黄金投资分析师，请基于当前市场数据为投资者提供黄金投资分析。

**当前市场数据：**
- 当前金价：{gold_price} 元/克
- 获取时间：{time_str}
- 数据来源：{source}

**分析要求：**
请按照以下格式提供专业的黄金投资分析，内容要具体、专业且有实用价值：

**黄金相关**：
▶ 地缘政治：（分析当前地缘政治对黄金的影响，如中东局势、俄乌冲突、台海局势等）
▶ 货币政策：（分析美联储、央行政策对黄金的影响，如利率决议、通胀数据等）
▶ 资金流向：（分析黄金ETF、期货市场的资金流向和价格走势）

**操作建议**（加仓/减仓/持有）：
▶ 核心依据：
  ✓ 地缘风险指数（升级/缓和）
  ✓ 美元与实际利率（美联储鹰/鸽信号）
  ✓ 技术支撑位（关键价格点位分析）

**注意事项：**
1. 请基于真实的市场逻辑进行分析
2. 避免过于绝对的预测，要体现风险提示
3. 分析要具体到具体的价格点位和时间框架
4. 语言要专业但易懂，适合普通投资者阅读
5. 每个要点后面可以添加:cite[数字]格式的引用标记（模拟引用）

请开始你的分析：
"""
            
            # 调用AI模型
            messages = [
                {
                    "role": "system", 
                    "content": "你是一位资深的黄金投资分析师，拥有20年的贵金属市场分析经验。你的分析准确、专业，深受投资者信赖。"
                },
                {
                    "role": "user", 
                    "content": prompt
                }
            ]
            
            response = self.chat_completion(
                messages=messages,
                model=model,
                temperature=temperature,
                max_tokens=2000
            )
            
            if "error" in response:
                return response
            
            # 整理返回结果
            from datetime import datetime
            return {
                "analysis": response["content"],
                "gold_price": gold_price,
                "price_time": time_str,
                "data_source": source,
                "model_used": response.get("model", model),
                "usage": response.get("usage"),
                "timestamp": datetime.now().strftime("%Y-%m-%d %H:%M:%S")
            }
            
        except Exception as e:
            return {"error": f"生成黄金投资分析时出错: {e}"}


def get_real_time_gold_price() -> tuple:
    """
    获取中国黄金实时金价（元/克）和当前时间
    数据来源：金投网 (https://quote.cngold.org/gjs/swhj_zghj.html)
    
    Returns:
        tuple: (金价(元/克), 当前时间字符串)
    """
    from datetime import datetime
    
    try:
        headers = {
            'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36'
        }
        
        # 方案1: 从金投网获取中国黄金价格
        try:
            url = "https://quote.cngold.org/gjs/swhj_zghj.html"
            response = requests.get(url, headers=headers, timeout=10)
            
            if response.status_code == 200:
                # 使用Selenium解析页面内容
                chrome_options = Options()
                chrome_options.add_argument("--headless")
                chrome_options.add_argument("--no-sandbox")
                chrome_options.add_argument("--disable-dev-shm-usage")
                chrome_options.add_argument("--disable-gpu")
                chrome_options.add_argument("--window-size=1920,1080")
                
                try:
                    from webdriver_manager.chrome import ChromeDriverManager
                    driver = webdriver.Chrome(
                        service=webdriver.chrome.service.Service(ChromeDriverManager().install()),
                        options=chrome_options
                    )
                except:
                    driver = webdriver.Chrome(options=chrome_options)
                
                try:
                    driver.get(url)
                    wait = WebDriverWait(driver, 10)
                    
                    # 等待页面加载完成，查找价格表格
                    # 根据网页结构，寻找包含价格信息的表格或元素
                    price_elements = driver.find_elements(By.CSS_SELECTOR, "table tr td")
                    
                    # 查找基础金价或零售价
                    for element in price_elements:
                        text = element.text.strip()
                        if text and text.replace('.', '').replace(',', '').isdigit():
                            try:
                                price = float(text)
                                if 400 <= price <= 800:  # 合理的金价范围
                                    current_time = datetime.now()
                                    time_str = current_time.strftime("%Y-%m-%d %H:%M:%S")
                                    
                                    print(f"中国黄金价格: {price} 元/克")
                                    print(f"获取时间: {time_str}")
                                    
                                    return (price, time_str)
                            except ValueError:
                                continue
                                
                finally:
                    driver.quit()
                    
        except Exception as e:
            print(f"金投网页面解析失败: {e}")
        
        # 方案2: 尝试从新浪财经获取上海黄金交易所数据（备选）
        try:
            url = "https://hq.sinajs.cn/list=hf_AU9999"
            response = requests.get(url, headers=headers, timeout=10)
            
            if response.status_code == 200 and response.text:
                data = response.text.strip()
                if 'hq_str_hf_AU9999=' in data:
                    price_data = data.split('"')[1].split(',')
                    if len(price_data) > 8:
                        current_price = float(price_data[8])
                        current_time = datetime.now()
                        time_str = current_time.strftime("%Y-%m-%d %H:%M:%S")
                        
                        print(f"上海黄金交易所Au9999价格: {current_price} 元/克")
                        print(f"获取时间: {time_str}")
                        
                        return (current_price, time_str)
        except Exception as e:
            print(f"新浪财经API调用失败: {e}")
        
        # 方案2: 尝试从东方财富获取上海黄金交易所数据
        try:
            # 东方财富的上海黄金交易所数据接口
            url = "http://push2.eastmoney.com/api/qt/stock/get"
            params = {
                'secid': '113.au9999',  # 上海黄金交易所Au9999
                'fields': 'f43,f57,f58,f169,f170,f46,f44,f51,f168,f47,f164,f163,f116,f60,f45,f52'
            }
            
            response = requests.get(url, params=params, headers=headers, timeout=10)
            
            if response.status_code == 200:
                data = response.json()
                if 'data' in data and data['data']:
                    price = data['data'].get('f43')  # 最新价
                    if price:
                        price = price / 1000  # 转换为元/克
                        current_time = datetime.now()
                        time_str = current_time.strftime("%Y-%m-%d %H:%M:%S")
                        
                        print(f"上海黄金交易所Au9999价格: {price} 元/克")
                        print(f"获取时间: {time_str}")
                        
                        return (price, time_str)
        except Exception as e:
            print(f"东方财富API调用失败: {e}")
        
        # 方案3: 使用配置的付费API（如极速数据等）
        try:
            config_file = "config.json"
            if os.path.exists(config_file):
                with open(config_file, 'r', encoding='utf-8') as f:
                    config = json.load(f)
                    api_key = config.get('gold_api_key')
                    
                    if api_key and api_key != "your_gold_api_key_here":
                        # 极速数据API示例
                        url = "https://api.jisuapi.com/gold/shgold"
                        params = {'appkey': api_key}
                        
                        response = requests.get(url, params=params, headers=headers, timeout=10)
                        
                        if response.status_code == 200:
                            data = response.json()
                            if data.get('status') == 0 and 'result' in data:
                                # 查找Au9999数据
                                for item in data['result']:
                                    if item.get('type') == 'Au99.99' or item.get('typename') == '沪金99':
                                        price = float(item.get('price', 0))
                                        current_time = datetime.now()
                                        time_str = current_time.strftime("%Y-%m-%d %H:%M:%S")
                                        
                                        print(f"上海黄金交易所Au9999价格: {price} 元/克")
                                        print(f"获取时间: {time_str}")
                                        
                                        return (price, time_str)
        except Exception as e:
            print(f"付费API调用失败: {e}")
        
        # 备选方案: 模拟中国黄金价格数据（用于演示）
        print("使用模拟数据（实际应用请配置真实API）")
        import random
        current_time = datetime.now()
        
        # 模拟中国黄金价格（基于2024年的大致金价）
        base_price = 552.0  # 基础金价（元/克）
        fluctuation = random.uniform(-5, 5)  # 随机波动
        gold_price = round(base_price + fluctuation, 2)
        
        time_str = current_time.strftime("%Y-%m-%d %H:%M:%S")
        
        print(f"模拟中国黄金价格: {gold_price} 元/克")
        print(f"获取时间: {time_str}")
        
        return (gold_price, time_str)
        
    except Exception as e:
        print(f"获取金价时出错: {e}")
        # 返回默认值
        current_time = datetime.now()
        return (0.0, current_time.strftime("%Y-%m-%d %H:%M:%S"))


def get_nasdaq_index() -> float:
    """
    获取纳斯达克综合指数(NASDAQ Composite Index)当前或收盘点数
    数据来源：东方财富网 (https://quote.eastmoney.com/gb/zsNDX.html)
    
    Returns:
        float: 纳斯达克综合指数点数
    """
    try:
        headers = {
            'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36'
        }
        
        # 方案1: 从东方财富网获取纳斯达克指数
        try:
            url = "https://quote.eastmoney.com/gb/zsNDX.html"
            
            # 使用Selenium解析页面内容
            chrome_options = Options()
            chrome_options.add_argument("--headless")
            chrome_options.add_argument("--no-sandbox")
            chrome_options.add_argument("--disable-dev-shm-usage")
            chrome_options.add_argument("--disable-gpu")
            chrome_options.add_argument("--window-size=1920,1080")
            
            try:
                from webdriver_manager.chrome import ChromeDriverManager
                driver = webdriver.Chrome(
                    service=webdriver.chrome.service.Service(ChromeDriverManager().install()),
                    options=chrome_options
                )
            except:
                driver = webdriver.Chrome(options=chrome_options)
            
            try:
                driver.get(url)
                wait = WebDriverWait(driver, 10)
                
                # 等待页面加载完成，查找纳斯达克指数价格
                # 尝试多种可能的选择器来获取价格
                price_selectors = [
                    ".price",
                    ".current-price", 
                    ".quote-price",
                    "[data-field='price']",
                    ".stock-price",
                    ".index-price"
                ]
                
                for selector in price_selectors:
                    try:
                        price_element = wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, selector)))
                        price_text = price_element.text.strip()
                        
                        # 提取数字
                        import re
                        price_match = re.search(r'[\d,]+\.?\d*', price_text.replace(',', ''))
                        if price_match:
                            price = float(price_match.group().replace(',', ''))
                            if 10000 <= price <= 25000:  # 合理的纳斯达克指数范围
                                print(f"纳斯达克综合指数: {price:.2f} 点")
                                return round(price, 2)
                    except:
                        continue
                
                # 如果上述选择器都不工作，尝试查找包含数字的元素
                all_elements = driver.find_elements(By.CSS_SELECTOR, "*")
                for element in all_elements:
                    try:
                        text = element.text.strip()
                        if text and ',' in text:
                            # 尝试解析可能的价格
                            import re
                            price_match = re.search(r'(\d{2,5}[,.]?\d{2,3}\.?\d{0,2})', text.replace(',', ''))
                            if price_match:
                                price_str = price_match.group(1).replace(',', '')
                                price = float(price_str)
                                if 10000 <= price <= 25000:  # 合理的纳斯达克指数范围
                                    print(f"纳斯达克综合指数: {price:.2f} 点")
                                    return round(price, 2)
                    except:
                        continue
                        
            finally:
                driver.quit()
                
        except Exception as e:
            print(f"东方财富网页面解析失败: {e}")
        
        # 方案2: 使用Yahoo Finance API获取纳斯达克综合指数（备选）
        try:
            import yfinance as yf
            # 纳斯达克综合指数的正确代码是^IXIC
            nasdaq = yf.Ticker("^IXIC")
            info = nasdaq.info
            
            # 优先获取实时价格
            if 'regularMarketPrice' in info:
                current_price = info['regularMarketPrice']
                print(f"纳斯达克综合指数(^IXIC): {current_price:.2f} 点")
                return round(current_price, 2)
            
            # 如果没有实时价格，获取历史数据的最新收盘价
            hist = nasdaq.history(period="1d")
            if not hist.empty:
                current_price = hist['Close'].iloc[-1]
                print(f"纳斯达克综合指数(^IXIC): {current_price:.2f} 点")
                return round(current_price, 2)
                
        except ImportError:
            print("yfinance库未安装，请运行: pip install yfinance")
        except Exception as e:
            print(f"Yahoo Finance API调用失败: {e}")
        
        # 方案2: 通过Yahoo Finance的Web API直接获取
        try:
            url = "https://query1.finance.yahoo.com/v8/finance/chart/%5EIXIC"
            response = requests.get(url, headers=headers, timeout=10)
            
            if response.status_code == 200:
                data = response.json()
                if ('chart' in data and 'result' in data['chart'] and 
                    data['chart']['result'] and len(data['chart']['result']) > 0):
                    
                    result = data['chart']['result'][0]
                    
                    # 获取实时价格
                    if 'meta' in result and 'regularMarketPrice' in result['meta']:
                        price = result['meta']['regularMarketPrice']
                        print(f"纳斯达克综合指数(^IXIC): {price:.2f} 点")
                        return round(price, 2)
                    
                    # 如果没有实时价格，获取最新的收盘价
                    if ('indicators' in result and 'quote' in result['indicators'] and
                        result['indicators']['quote'] and len(result['indicators']['quote']) > 0):
                        quote = result['indicators']['quote'][0]
                        if 'close' in quote and quote['close']:
                            close_prices = [p for p in quote['close'] if p is not None]
                            if close_prices:
                                price = close_prices[-1]
                                print(f"纳斯达克综合指数(^IXIC): {price:.2f} 点")
                                return round(price, 2)
                                
        except Exception as e:
            print(f"Yahoo Finance Web API调用失败: {e}")
        
        # 方案3: 从新浪财经获取纳斯达克指数
        try:
            url = "https://hq.sinajs.cn/list=gb_ixic"
            response = requests.get(url, headers=headers, timeout=10)
            
            if response.status_code == 200 and response.text:
                data = response.text.strip()
                if 'hq_str_gb_ixic=' in data:
                    # 解析新浪财经返回的数据格式
                    price_data = data.split('"')[1].split(',')
                    if len(price_data) > 1:
                        current_price = float(price_data[1])  # 最新价
                        print(f"纳斯达克综合指数(^IXIC): {current_price:.2f} 点")
                        return round(current_price, 2)
                        
        except Exception as e:
            print(f"新浪财经API调用失败: {e}")
        
        # 方案4: 使用配置的付费API
        try:
            config_file = "config.json"
            if os.path.exists(config_file):
                with open(config_file, 'r', encoding='utf-8') as f:
                    config = json.load(f)
                    api_key = config.get('stock_api_key')
                    
                    if api_key and api_key != "your_stock_api_key_here":
                        # 这里可以添加付费API的调用逻辑
                        # 例如: Alpha Vantage, IEX Cloud等
                        pass
        except Exception as e:
            print(f"付费API调用失败: {e}")
        
        # 备选方案: 模拟数据（用于演示）
        print("使用模拟数据（实际应用请配置真实API）")
        import random
        
        # 模拟纳斯达克综合指数在合理范围内波动（基于2024年的大致范围）
        base_index = 16000.0  # 基础指数（更新为2024年的合理水平）
        fluctuation = random.uniform(-300, 300)  # 随机波动
        nasdaq_index = round(base_index + fluctuation, 2)
        
        print(f"模拟纳斯达克综合指数: {nasdaq_index:.2f} 点")
        return nasdaq_index
        
    except Exception as e:
        print(f"获取纳斯达克指数时出错: {e}")
        return 0.0



# 使用示例
if __name__ == "__main__":
    print("=== FinaMaker 工具演示 ===")
    
    # 获取MSN网站内容
    print("\n1. 获取MSN网站内容...")
    msn_content = get_msn_content()
    
    # 获取实时金价
    print("\n2. 获取中国黄金价格...")
    gold_price, time_str = get_real_time_gold_price()
    print(f"金价: {gold_price} 元/克，时间: {time_str}")
    
    # 获取纳斯达克指数
    print("\n3. 获取纳斯达克综合指数...")
    nasdaq_index = get_nasdaq_index()
    print(f"纳斯达克综合指数: {nasdaq_index} 点")
    
    # 初始化OpenAI客户端
    print("\n4. 初始化OpenAI客户端...")
    openai_client = OpenAIClient()
    
    # 示例：使用聊天完成API
    if openai_client.client:
        print("\n5. 测试OpenAI API...")
        messages = [
            {"role": "user", "content": "你好，请简单介绍一下自己"}
        ]
        response = openai_client.chat_completion(messages)
        print("API响应:", response)
    else:
        print("\n5. OpenAI客户端未初始化")
        print("请参考 config.example.json 创建 config.json 配置文件")
    
    print("\n=== 演示完成 ===")
